package com.wudd.common.util.locationUtils;

import java.lang.reflect.Method;
import java.math.BigDecimal;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.wudd.common.enums.CoordinateType;

/**
 * @ClassName: GeoUtil
 * @description:
 * @author: liule
 * @date: 2018/9/18 20:28
 * @modified by:
 */
public class GeoUtil {
	private static Logger logger = LoggerFactory.getLogger(GeoUtil.class);
	/**
	 * Longitude 计算半径经纬度对应长度（经度） 1度对应85.39km WGS1984的经纬度坐标 经度1度=85.39km 经度1分 = 1.42km 经度1秒 = 23.6m
	 *
	 * @author ycj
	 * @date 2014-04-03
	 */
	public static double getLon(double km) {
		return km / 85.39;
	}

	/**
	 * Latitude 计算半径经纬度对应长度（纬度） 1度对应111km WGS1984的经纬度坐标 纬度1度 = 大约111km 纬度1分 = 大约1.85km 纬度1秒 = 大约30.9m
	 *
	 * @author ycj
	 * @date 2014-04-03
	 */
	public static double getLat(double km) {
		return km / 111;
	}

	public static double distance(double A2, double B2, double C2, double D2) {
		double d = 6371004 * Math.acos((Math.sin(Math.toRadians(B2)) * Math.sin(Math.toRadians(D2)) + Math.cos(Math.toRadians(B2)) * Math.cos(Math.toRadians(D2))
				* Math.cos(Math.toRadians(C2 - A2))));
		return d;
	}

	public static void main(String[] args) {
		double d1 = distance(116.69546, 39.583514, 116.69586, 39.583544);// 34.44099858125905
		double d2 = 0;
		long time = System.currentTimeMillis();
		//      for (int i = 0; i < 10000; i++)
		d2 = GetDistance(116.69546, 39.583514, 116.69586, 39.583544);
		System.out.println(System.currentTimeMillis() - time);
		System.out.println(d1 + "\n" + d2);
	}

	// latitude 纬度 lat 116.69546 116.69586
	// longitude 经度 lon 39.583514 39.583544
	// google map
	private static double EARTH_RADIUS = 6378137;

	// google map
	private static double rad(double d) {
		return d * Math.PI / 180.0;
	}

	// google map
	public static double GetDistance(double lng1, double lat1, double lng2, double lat2) {
		double radLat1 = rad(lat1);
		double radLat2 = rad(lat2);
		double a = radLat1 - radLat2;
		double b = rad(lng1) - rad(lng2);
		double s = 2 * Math.asin(Math.sqrt(Math.pow(Math.sin(a / 2), 2) + Math.cos(radLat1) * Math.cos(radLat2) * Math.pow(Math.sin(b / 2), 2)));
		s = s * EARTH_RADIUS;
		s = Math.round(s * 10000) / 10000;
		return s;
	}

	@SuppressWarnings({ "unchecked", "rawtypes" })
	public static <T> void goeTransformation(T data, CoordinateType sourceType, CoordinateType targetType) {
		if (sourceType == null || targetType == null) {
			return;
		}
		Class cls = data.getClass();
		try {
			Method longitudeGetMethod = cls.getMethod("getLongitude");
			Method latitudeGetMethod = cls.getMethod("getLatitude");
			Method longitudeSetMethod = cls.getMethod("setLongitude", BigDecimal.class);
			Method latitudeSetMethod = cls.getMethod("setLatitude", BigDecimal.class);
			Object longitude = longitudeGetMethod.invoke(data);
			Object latitude = latitudeGetMethod.invoke(data);
			if (longitude == null || latitude == null) {
				return;
			}
			GpsUtil.Gps gps = CoordinatesUtil.transformCoordinates(sourceType, ((BigDecimal)latitude).doubleValue(),
					((BigDecimal)longitude).doubleValue(), targetType);
			longitudeSetMethod.invoke(data, new BigDecimal(gps.getLongitude()));
			latitudeSetMethod.invoke(data, new BigDecimal(gps.getLatitude()));
		} catch (NoSuchMethodException e) {
			logger.error("方法未找到", e);
		}catch (Exception e) {
			logger.error("方法调用异常", e);
		}
	}

	/*public static void main(String args) {
		PartOrder partOrder = new PartOrder();
		partOrder.setLatitude(new BigDecimal("30.2341"));
		partOrder.setLongitude(new BigDecimal("120.241324"));
		GeoUtil.goeTransformation(partOrder, CoordinateType.BD09, CoordinateType.WGS84);
	}*/
}
